﻿using System;
using System.Collections.Generic;
using MugenInjection.Core;
using MugenInjection.Delegates;
using MugenInjection.Infrastructure;
using MugenInjection.Interface;
using MugenInjection.Scope;

namespace MugenInjection.Bindings
{
    /// <summary>
    /// Represents the constant binding.
    /// </summary>
    public class ConstantBinding : BindingBase
    {
        #region Nested type : ConstantScope

        private sealed class ConstantScope : ScopeLifecycleBase
        {
            #region Fields

            private readonly object _value;

            #endregion

            #region Constructors

            /// <summary>
            ///     Initializes a new instance of the <see cref="ConstantScope" /> class.
            /// </summary>
            public ConstantScope(object value)
            {
                _value = value;
            }

            #endregion

            #region Overrides of ScopeLifecycleBase

            /// <summary>
            ///     Resolves instance for the specified <see cref="IBindingContext" /> from scope.
            /// </summary>
            /// <returns>An instance of the service.</returns>
            protected override object GetObjectFromScope()
            {
                return _value;
            }

            /// <summary>
            ///     Gets all created objects in the current scope.
            /// </summary>
            protected override IList<object> GetObjectsFromScope()
            {
                return InjectorUtilsInternal.EmptyParams;
            }

            /// <summary>
            ///     Clears the current scope.
            /// </summary>
            protected override void ClearScope()
            {
            }

            /// <summary>
            ///     Releases resources held by the object.
            /// </summary>
            protected override void Dispose(bool disposing)
            {
                if (disposing)
                    TryReleaseObjectWithNotification(_value);
            }

            #endregion
        }

        #endregion

        #region Fields

        private readonly object _value;

        #endregion

        #region Constructor

        /// <summary>
        /// Initializes a new instance of the <see cref="ConstantBinding" /> class.
        /// </summary>
        /// <param name="value">Constant value.</param>
        /// <param name="services">The specified services types.</param>
        /// <param name="parameters">The specified parameters.</param>
        /// <param name="canResolve">The specified condition for can resolve method.</param>
        public ConstantBinding(object value, IList<Type> services, IEnumerable<IInjectionParameter> parameters, CanResolveBindingDelegate canResolve)
            : base(services, new ConstantScope(value), parameters, canResolve)
        {
            _value = value;
        }

        #endregion

        #region Overrides of BindingBase

        /// <summary>
        /// Resolves instance for the specified <see cref="IBindingContext"/>.
        /// </summary>
        /// <param name="bindingContext">The specified <see cref="IBindingContext"/>.</param>
        /// <returns>An instance of the service.</returns>
        protected override object ResolveService(IBindingContext bindingContext)
        {
            return _value;
        }

        #endregion
    }
}